package com.web.exiaodao.business.service.impl;

import com.alibaba.fastjson.JSON;
import com.google.common.base.Function;
import com.web.exiaodao.business.entity.Category;
import com.web.exiaodao.business.entity.News;
import com.web.exiaodao.business.repository.CategoryRepository;
import com.web.exiaodao.business.repository.NewsRepository;
import com.web.exiaodao.business.service.NewsService;
import com.web.exiaodao.remote.vo.CategoryVo;
import com.web.exiaodao.remote.vo.NewsVo;
import com.web.webstart.base.constant.XaConstant;
import com.web.webstart.base.exception.BaseException;
import com.web.webstart.base.exception.BusinessException;
import com.web.webstart.base.service.impl.BaseService;
import com.web.webstart.base.util.XaUtil;
import com.web.webstart.base.util.jpa.DynamicSpecifications;
import com.web.webstart.base.util.jpa.MyPage;
import com.web.webstart.base.util.jpa.SearchFilter;
import com.web.webstart.base.util.jpa.SearchFilter.Operator;
import com.web.webstart.base.util.result.XaResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service("NewsService")
@Transactional(readOnly = false)
public class NewsServiceImpl extends BaseService<NewsVo> implements NewsService {

	@Autowired
	private NewsRepository newsRepository;


	@Autowired
	private CategoryRepository shopCategoryRepository;

	/**
	 * 查询单条News信息
	 * @return 返回单个News对象
	 * @throws BusinessException
	 */
	@Transactional(readOnly = true, rollbackFor = Exception.class)
	public XaResult<NewsVo> findOne(Long modelId) throws BusinessException {
		News obj = new News();
		if(modelId != 0){
			obj = newsRepository.findByIdAndStatusNot(modelId,XaConstant.Status.delete);
		}
		XaResult<NewsVo> xr = new XaResult<>();
		if (XaUtil.isNotEmpty(obj)) {
			xr.setObject(JSON.parseObject(JSON.toJSONString(obj), NewsVo.class));
		} else {
			throw new BusinessException(XaConstant.Message.object_not_find);
		}
		return xr;
	}

	/**
	 * 分页查询状态非status的News数据
	 * @param status
	 * @param filterParams
	 * @param pageable
	 * @return 返回对象News集合
	 * @throws BusinessException
	 */
	@Transactional(readOnly = true, rollbackFor = Exception.class)
	public XaResult<Page<NewsVo>> findListNEStatusByFilter(
			Integer status, Map<String, Object> filterParams, Pageable pageable) throws BusinessException {
		Map<String, SearchFilter> filters = SearchFilter.parse(filterParams);
		if(status == null){// 默认显示非删除的所有数据
			status = XaConstant.Status.delete;
		}
		filters.put("status", new SearchFilter("status", Operator.NE, status));
		Page<News> page = newsRepository.findAll(DynamicSpecifications
				.bySearchFilter(filters.values(), News.class), pageable);
		XaResult<Page<NewsVo>> xr = new XaResult<Page<NewsVo>>();
		xr.setObject(new MyPage<>(page, JSON.parseArray(JSON.toJSONString(page.getContent()), NewsVo.class)));

		//查询分类信息
		Map<String, SearchFilter> categoryFilters = new HashMap<>();
		categoryFilters.put("status", filters.get("status"));
		List<Category> categories = shopCategoryRepository.findAll(DynamicSpecifications
				.bySearchFilter(categoryFilters.values(), Category.class));
		Map<String,Category> categoryMap = com.web.webstart.base.util.CollectionUtils.listToMap(categories != null ? categories.iterator() : null, new Function<Category, String>() {
			@Override
			public String apply(Category shopCategory) {
				return shopCategory.getId().toString();
			}
		});

		//拼装数据
		List<NewsVo> data = xr.getObject().getContent();
		for (int i = 0 ; categoryMap != null && data != null && i < data.size(); ++i) {
			long type =  -1;
			if(XaUtil.isNotEmpty(data.get(i).getType())){
				type =  data.get(i).getType();
			}
			Category category = categoryMap.get(type+"");
			data.get(i).setCategoryVo(JSON.parseObject(JSON.toJSONString(category), CategoryVo.class));
		}
		return xr;
	}

	/**
	 * 分页查询状态status的News数据
	 * @param status
	 * @param filterParams
	 * @param pageable
	 * @return 返回对象News集合
	 * @throws BusinessException
	 */
	@Transactional(readOnly = true, rollbackFor = Exception.class)
	public XaResult<Page<NewsVo>> findListEQStatusByFilter(
			Integer status, Map<String, Object> filterParams, Pageable pageable) throws BusinessException {
		Map<String, SearchFilter> filters = SearchFilter.parse(filterParams);
		if(status == null){// 默认显示正常数据
			status = XaConstant.Status.valid;
		}
		filters.put("status", new SearchFilter("status", Operator.EQ, status));
		Page<News> page = newsRepository.findAll(DynamicSpecifications
				.bySearchFilter(filters.values(), News.class), pageable);
		XaResult<Page<NewsVo>> xr = new XaResult<>();
		xr.setObject(new MyPage<>(page, JSON.parseArray(JSON.toJSONString(page.getContent()), NewsVo.class)));
		return xr;
	}


	/**
	 * 保存News信息
	 * @param model
	 * @return
	 * @throws BusinessException
	 */
	@Transactional(rollbackFor = Exception.class)
	public XaResult<NewsVo> saveOrUpdate(NewsVo model) throws BusinessException {
		News obj = null;
		if(XaUtil.isNotEmpty(model.getId())){
			obj = newsRepository.findOne(model.getId());
		}else{
			obj = new News();
		}
		obj.setTitle(XaUtil.isNotEmpty(model.getTitle()) ? model.getTitle() : obj.getTitle());
		obj.setSource(XaUtil.isNotEmpty(model.getSource()) ? model.getSource() : obj.getSource());
		obj.setThumbnail(XaUtil.isNotEmpty(model.getThumbnail()) ? model.getThumbnail() : obj.getThumbnail());
		obj.setContent(XaUtil.isNotEmpty(model.getContent()) ? model.getContent() : obj.getContent());
		obj.setIsHot(XaUtil.isNotEmpty(model.getIsHot()) ? model.getIsHot() : obj.getIsHot());
		obj.setType(XaUtil.isNotEmpty(model.getType()) ? model.getType() : obj.getType());
		obj = newsRepository.save(obj);
		XaResult<NewsVo> xr = new XaResult<>();
		xr.setObject(JSON.parseObject(JSON.toJSONString(obj), NewsVo.class));
		return xr;
	}

	/**
	 * 修改News状态，可一次修改多条   3删除  -1锁定  1正常
	 * @param modelIds
	 * @param status
	 * @return 返回News对象
	 * @throws BusinessException
	 */
	@Transactional(rollbackFor = Exception.class)
	public XaResult<NewsVo> multiOperate(
			String modelIds,Integer status) throws BusinessException {
		XaResult<NewsVo> xr = new XaResult<>();
		if(status == null){
			status = XaConstant.Status.delete;
		}
		if(modelIds != null){
			String[] ids = modelIds.split(",");
			for(String id : ids){
				News obj = newsRepository.findByIdAndStatusNot(Long.parseLong(id),status);
				if (XaUtil.isNotEmpty(obj)) {
					obj.setStatus(status);
					obj = newsRepository.save(obj);
				} else {
					throw new BusinessException(XaConstant.Message.object_not_find);
				}
			}
		}
		return xr;
	}

    @Override
    public XaResult<Long> findShopCountByCategoryType(Long categoryType) throws BaseException {
        XaResult<Long> xr = new XaResult<>();
        long count =  newsRepository.findNewsCountByCategoryIdAndStatusNot(categoryType, XaConstant.Status.delete);
        xr.setObject(count);
        return xr;
    }

}
